/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package br.com.deployment.servicoimpl;

import br.com.deployment.entidade.acesso.Usuario;
import br.com.deployment.entidade.empresa.Cartorio;
import br.com.deployment.entity.orcamento.Orcamento;
import br.com.deployment.entidade.fermojupi.AtoItem;
import br.com.deployment.entidade.humana.Pessoa;
import br.com.deployment.entidade.protocolo.Protocolo;
import br.com.deployment.entity.orcamento.OrcamentoAto;
import br.com.deployment.entity.orcamento.OrcamentoCampo;
import br.com.deployment.enums.Relatorio;
import br.com.deployment.interfaces.OrcamentoDaoIn;
import br.com.deployment.servico.*;
import br.com.deployment.utilitario.GeraRelatorio;
import br.com.deployment.utilitario.Msg;
import java.io.*;
import java.math.BigDecimal;
import java.math.BigInteger;
import java.text.DecimalFormat;
import java.text.SimpleDateFormat;
import java.util.*;
import javax.ejb.*;
import javax.faces.context.FacesContext;
import javax.persistence.NoResultException;

/**
 *
 * @author roniere
 */
@Stateless
@LocalBean
public class OrcamentoServicoImpl implements OrcamentoServico{
    
    @EJB
    OrcamentoDaoIn orcamentoDao;
    
    @EJB
    EmolumentoServico emolumentoDao;
    
    @EJB
    PessoaServico pessoaDao;
    
    @EJB
    OrcamentoAtoServico orcamentoAtoServico;
    
    @EJB
    ProtocoloServico protocoloServico;
    
    @EJB
    CartorioServico cartorioDao;
    
    private boolean salvo = false;
    
    
    @Override
    public boolean getSalvo(){
        return salvo;
    }

    @Override
    public Orcamento salvar(Orcamento o) {
        try{
            if(!o.getOrcamentoAtos().isEmpty()){
                o = salvarOrcamento(o);
                
                return o;
            }else{
                Msg.messagemError("Orçamento deve conter Serviços");
            }
            
        }catch(EJBAccessException accessException){
            Msg.messagemError("Erro no EJB");
            System.err.println("ERRO NO EJB");
        }   
        return o;
        
    }
    
    
    
    public boolean exist(Orcamento o){
        return orcamentoDao.exist(o.getId());
    }
    
    @Override
    public Orcamento find(int id){
        return orcamentoDao.find(id);
    }
    
    private Orcamento salvarOrcamento(Orcamento o){
        if(exist(o)){
            
            o.setDataCadastro(new Date());
            
            if(o.getValidade() == null){
                o.setValidade(validade());
            }
            
            o = orcamentoDao.salvar(o);
            salvo = true;
            
            Msg.messagemInfo("Orçamento salvo com Sucesso");
        }else{
            
            if(o.getValidade() == null){
                o.setValidade(validade());
            }
            
            atualizar(o);
            
        }
        
         return o;
    }
    
    // TODO Mudar para ENUM
    public Integer getValidadeResourceBundle(){
        ResourceBundle resourceBundle;  
        resourceBundle = ResourceBundle.getBundle("br/com/deployment/resources/Messages");  
        Integer validade = Integer.parseInt(resourceBundle.getString("validade")); 
        return validade;
    }
    
    public Date validade(){
        SimpleDateFormat sd = new SimpleDateFormat("dd/MM/yyyy");
        Locale brasil = new Locale("pt","br");
        Calendar c = new GregorianCalendar(brasil);                  
        c.add(Calendar.DAY_OF_MONTH, getValidadeResourceBundle());  
        return c.getTime();   

    }

    @Override
    public void remover(Orcamento o) {
        try {
            orcamentoDao.delete(o);
        }catch(EJBAccessException accessException){
            Msg.messagemError("Erro no EJB");
        }catch (Exception e) {
            Msg.messagemError("Erro");
        }
    }

    @Override
    public void atualizar(Orcamento o) {
        try {
            orcamentoDao.update(o);
            Msg.messagemInfo("Atualizado com Sucesso");
        }catch(EJBAccessException accessException){
            Msg.messagemError("Erro no EJB");
        }catch (Exception e) {
            Msg.messagemError("Erro");
        }
    }

    @Override
    public List<Orcamento> orcamentos() {
        try {
            return orcamentoDao.findAll();
        }catch(EJBAccessException accessException){
            Msg.messagemError("Erro no EJB");
            System.err.println("ERRO NO EJB");
        }catch (Exception e) {
            Msg.messagemError("Erro");
            System.err.println("ERRO");
        }
        return null;
    }
    
    @Override
    public BigDecimal valorAto(AtoItem ai, BigDecimal valor){  
        boolean pesquisar = true;
        BigDecimal valorAto = new BigDecimal(0);
        
        pesquisar = emolumentoDao.verificaEmolumentoItemAto(ai);
        
        if(!pesquisar){
             Msg.messagemWarn("Ato inexistente na tabela de Emolumento");           
             throw new NumberFormatException();
        }
        
        try{
            valorAto = emolumentoDao.valorToAto(ai, valor);
        }catch(EJBException x){
            
            DecimalFormat df = new DecimalFormat("#,##0.00");
            String aux = String.valueOf(df.format(valor));
            
            Msg.messagemWarn("Valor "+aux+" relativo ao Ato: "+ai.getDescricao()+" inexiste na tabela de Emolumento.");
            throw new NoResultException();
        }
        return valorAto;
        
    }
    
    @Override
    public BigDecimal valorAto(OrcamentoAto aa){  
        System.err.println("Orcamento"+aa.getAtoItem());
         BigDecimal valor = new BigDecimal(BigInteger.ZERO);
         
        if (aa.getAtoItem() != null) {
            if (!aa.getOrcamentoCampos().isEmpty()) {
                for (OrcamentoCampo oc : aa.getOrcamentoCampos()) {
                        if (oc.getAtoCampo().getCalc()) {
                            valor = valorAto(aa.getAtoItem(), format(oc.getValor()));
                            oc.setOrcamentoAto(aa);
                            break;
                        }else if(oc.getAtoCampo().getMaster()){
                            valor = (format(oc.getValor()));
                            oc.setOrcamentoAto(aa);
                            break;
                        }
                    
                }
                return valor;
            }else{
                valor = valorAto(aa.getAtoItem(), new BigDecimal(BigInteger.ZERO));
                
            }
            
        } else {
            Msg.messagemError("O campo 'Ato' é obrigatório");
            return null;
        }
        return valor;
    }
    
     private BigDecimal format(String c) {

        c = c.replace(".", "").replaceAll(",", ".");
        BigDecimal val = new BigDecimal(c);
        return val;

    }
    
    
    @Override
    public Pessoa findDoc(String doc){
        Pessoa p = new Pessoa();
        try{
            p = pessoaDao.findDoc(doc);
        }catch(Exception nu){
            Msg.messagemError("Nenhum Usuário encontrado");
        }
        return p;
    }
    
    @Override
    public List<Orcamento> pesquisar(Orcamento o, Integer cod){
        try{
            List<Orcamento> listOrc = orcamentoDao.pesquisar(o, cod);

            if(!listOrc.isEmpty()){
                return listOrc;
            }else{
                return new ArrayList<Orcamento>();
            }
        }catch(NoResultException nu){
            System.err.println("ERRO NO NULL");
            return new ArrayList<Orcamento>();
        }catch(Exception e){
            Msg.messagemError("Erro: "+e);
            System.err.println("ERRO NO EX");
            return new ArrayList<Orcamento>();
        }
        
    }
    
    public FileInputStream getFile() throws FileNotFoundException{
        FacesContext facesContext = FacesContext.getCurrentInstance();
        String report = facesContext.getExternalContext().getRealPath("/relatorio/orcamento.jasper");
        FileInputStream fis = new FileInputStream (new File (report)); 
        return fis;
    }
    

    
    @Override
    public void imprimirOrcamento(Orcamento orc, Usuario usr){
            GeraRelatorio geraRelatorio = new GeraRelatorio();
        
            HashMap<String, Object> parametros;
            parametros = new HashMap<String, Object>();
            
            parametros.put("id", orc.getId());
            parametros.put("nome", orc.getNome());
            parametros.put("doc", orc.getDoc());
            
            BigDecimal valor = BigDecimal.ZERO;
            for ( OrcamentoAto object : orc.getOrcamentoAtos()) {
                valor = valor.add(object.getValor());
            }
            parametros.put("total", valor);
            parametros.put("usuario", usr.getNome());
            parametros.put("cargo", usr.getCargo());
            parametros.put("obs", orc.getObservacao());
            parametros.put("validade", orc.getValidade());
            
//            URL subreport = Thread.currentThread().getContextClassLoader().getResource("br/com/deployment/relatorios/orcamentoItem.jasper");
//            parametros.put("SUBREPORT_DIR", subreport.toString().replace("orcamentoItem.jasper", ""));
            parametros = getCartorio(parametros);
            orc.setOrcamentoAtos(orcamentoAtoServico.getOrcamento(orc));
            
            geraRelatorio.relatorio(parametros, orc.getOrcamentoAtos(), Relatorio.ORCAMENTO);
        
    }
    
    
    
    public HashMap<String, Object> getCartorio(HashMap<String, Object> parametros){      
            Cartorio cartorio = new Cartorio();
        
            cartorio = cartorioDao.getCartorioContext();
            
            String nomeTitulo = ""+cartorio.getTitular().getNome();
            String endereco = ""+cartorio.getEndereco().getTipo_logradouro().toString().toUpperCase() + " " +cartorio.getEndereco().getLogradouro() + " - " + cartorio.getEndereco().getTelefone();
            String cidade = ""+cartorio.getEndereco().getCidade().getNom_cidade().toUpperCase() + " - " + cartorio.getEndereco().getEstado().getNom_estado().toUpperCase();            
            
            parametros.put("cartorioNome", cartorio.getNome());
            parametros.put("cartorioTitular", nomeTitulo);
            parametros.put("cartorioEndereco", endereco);
            parametros.put("cartorioCidade", cidade);
        
            return parametros;
    }
    
    @Override
    public Protocolo orcamentoToProtocolo(Orcamento o){
         return protocoloServico.orcamentoToProtocolo(o);
    }
    

}
